﻿using System.Collections.Generic;
using System.Linq;
using DataScripter.Database;
using DataScripter.Scripting;
using DataScripter.Scripting.Fluent;
using DataScripter.Scripting.InputSources;
using DataScripter.Scripting.ScriptDefinitions;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using Moq;

namespace DataScripter.UnitTests.EngineTests.IncludeDependencies
{
    [TestClass]
    public class WhenRequestingATableHavingThreeDependenciesAndIncludingAllThreeDependenciesExplicitly
    {
        private readonly IFluentTableScriptRequest _fluentTableRequest;
        private readonly IScriptDefinition _scriptDefinition;

        public WhenRequestingATableHavingThreeDependenciesAndIncludingAllThreeDependenciesExplicitly()
        {
            const string myTableName = "MyTableWithThreeDependencies";
            Mock<IDatabaseStructure> structureMock = Factories.DbStructureFactory.Create(myTableName,
                                                                                            new[]{"D1","D2","D3"}
                                                                                        );
            Engine engine = new Engine();

            IInputSource inputSource = new SqlServerInputSource("", engine);
            inputSource.RegisterType(structureMock.Object);
            engine.RegisterType(inputSource);


            _scriptDefinition = new ScriptDefinition("", engine);
            engine.RegisterType(_scriptDefinition);

            IList<IForeignKey> foreignKeys = structureMock.Object.GetTable(myTableName).ForeignKeys;
            _fluentTableRequest = _scriptDefinition.RequestScript(myTableName)
                .IncludeDependencies(new[]
                                         {
                                             foreignKeys.First(fk => fk.ReferencedTableName=="D2"),
                                             foreignKeys.First(fk => fk.ReferencedTableName=="D3"),
                                             foreignKeys.First(fk => fk.ReferencedTableName=="D1")
                                         });
        }

        [TestMethod]
        public void TableAndAllThreeDependenciesShouldBeAppendedToTablesCollection()
        {
            Assert.AreEqual(4, _scriptDefinition.ScriptRequests.Count);
        }

        [TestMethod]
        public void TableScriptRequestShouldExistInCollection()
        {
            Assert.IsTrue(_scriptDefinition.ScriptRequests.ContainsKey(_fluentTableRequest.Request.TableName));
        }

        [TestMethod]
        public void TableScriptRequestShouldBeTheSameInCollection()
        {
            Assert.IsTrue(_scriptDefinition.ScriptRequests[_fluentTableRequest.Request.TableName] == _fluentTableRequest.Request);
        }

        [TestMethod]
        public void FirstDependencyRequestShouldBeInCollection()
        {
            Assert.IsTrue(_scriptDefinition.ScriptRequests.ContainsKey("D2"));
        }
        [TestMethod]
        public void SecondDependencyRequestShouldBeInCollection()
        {
            Assert.IsTrue(_scriptDefinition.ScriptRequests.ContainsKey("D3"));
        }
        [TestMethod]
        public void ThirdDependencyRequestShouldBeInCollection()
        {
            Assert.IsTrue(_scriptDefinition.ScriptRequests.ContainsKey("D1"));
        }

    }
}
